package model;

import static org.junit.Assert.*;

import java.security.SecureRandom;
import org.junit.After;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;

public class HandTest{
	
	private Deck deck;
	private static SecureRandom Generator;
	private int handsAmount;
	private Hand hands[];
	private static int[][] theSameRanksHands;
	private static int[][] theSameSuitsHands;
	private Deck deckToDiscard;
	private Hand handsToDiscard[];
	
	@BeforeClass
	public static void setUpBeforeClass() throws Exception{
		Generator = new SecureRandom();
		theSameRanksHands = new int[13][4];
		for(int i=0; i<13; i++) {
			theSameRanksHands[i] = new int[]{i,13+i,26+i,39+i};
			for (int j=0; j<4; j++)
				System.out.println(theSameRanksHands[i][j]);
		}
		theSameSuitsHands = new int[4][4];
		for (int i=0; i<4; i++) {
			theSameSuitsHands[i] = new int[]{i*13,i*13+1,i*13+2,i*13+3};
			for (int j=0; j<4; j++)
				System.out.println(theSameSuitsHands[i][j]);
		}
		
	}

	@AfterClass
	public static void tearDownAfterClass() throws Exception{
		Generator = null;
		for(int i=0; i<13; i++)
			theSameRanksHands[i] = null;
			
		theSameRanksHands = null;
		for (int i=0; i<4; i++)
			theSameSuitsHands[i] = null;
		theSameSuitsHands = null;
	}

	@Before
	public void setUp() throws Exception{
		deck = new Deck();
		handsAmount = Generator.nextInt(5)+2;
		hands = new Hand[handsAmount+1];
		for (int i=1; i<=handsAmount; i++) {
			hands[i]= new Hand(deck, i);
		}
		deckToDiscard = new Deck();
		handsToDiscard = new Hand[10];
		for (int i=1; i<10; i++) {
			handsToDiscard[i]= new Hand(deckToDiscard, i);
		}
	}

	@After
	public void tearDown() throws Exception{
		for (int i=1; i<=handsAmount; i++) {
			hands[i]= null;
		}
		hands = null;
		deck = null;
	}

	@Test
	public void testHand(){
		for (int i=1; i<=handsAmount; i++) {
			assertNotNull(hands[i]);
		}		
	}

	@Test
	public void testGetReducedHand(){
		for(int i=0; i<13; i++)
			assertTrue(Hand.getReducedHand(theSameRanksHands[i]).length==1);
		for(int i=0; i<4; i++) {
			assertArrayEquals(new int[]{13*i},Hand.getReducedHand(theSameSuitsHands[i]));
		}
		assertArrayEquals(new int[]{1,15,30},Hand.getReducedHand(new int[]{1,15,28,30}));
		assertArrayEquals(new int[]{5,20},Hand.getReducedHand(new int[]{5,18,20,25}));
		assertArrayEquals(new int[]{29,43,9},Hand.getReducedHand(new int[]{29,30,43,9}));
	}
	@Test
	public void testGiveWorstCard(){
		for (int j=0; j<4; j++)
			assertEquals(3,Hand.giveWorstCard(theSameSuitsHands[j]));
		assertEquals(4,Hand.giveWorstCard(new int[]{1,15,28,30}));
		assertEquals(12,Hand.giveWorstCard(new int[]{5,18,20,25}));
		assertEquals(9,Hand.giveWorstCard(new int[]{29,30,43,9}));
		
	}

	@Test
	public void testDiscardAllCards(){
		for (int i=1; i<10; i++) {
			handsToDiscard[i].discardAllCards(deckToDiscard);
			assertArrayEquals(new int[]{-1,-1,-1,-1},handsToDiscard[i].getCards());
		}
	}

	@Test
	public void testDrawAllCards(){
		for (int i=1; i<10; i++) {
			handsToDiscard[i].discardAllCards(deckToDiscard);
		}
		for (int i=1; i<10; i++) {
			handsToDiscard[i].drawAllCards(deckToDiscard,i);
			for (int j=0; j<4; j++) {
				assertFalse("0-1"==handsToDiscard[i].getOneCard(j));;
			}
		}
	}
	@Test
	public void testChangeCards(){
		String[] oldCards = new String[10];
		for(int i=1; i<10; i++) {
			oldCards[i] = handsToDiscard[i].getString();
			handsToDiscard[i].changeCards(deckToDiscard, i, 13);
			assertFalse(oldCards[i].equals(handsToDiscard[i].getString()));
		}
	}
	

}
